(function($){
	
	$.fn.countRow=function(str){
        // Number of td's in the last table row
		//if $(this) is a table then return table row count , if $(this) is a tbody then return tbody row count. 
		var jqObj = $(this);
		var nodeObj = jqObj.get(0);
		return nodeObj.rows.length;
    };
	
	$.fn.addRow = function(str){
        // Number of td's in the last table row
		var jqObj = $(this);
		var nodeObj = jqObj.get(0);
		console.log('$(this).get(0).innerHTML:'+nodeObj);
		var ne = nodeObj.insertRow(-1);
		var buff = '';
		$.each(str,function(index,value){
			buff+= '<td>'+value+'</td>';
		});
		ne.innerHTML = buff;
    };
	
	$.fn.insertRow=function(index,str){
		var nodeObj = $(this).get(0);
		var total = nodeObj.rows.length;
		if(index !== NaN && index < total && index >= 0 ){
			var ne = nodeObj.insertRow(index);
			var buff = '';
			$.each(str,function(index,value){
				buff+= '<td>'+value+'</td>';
			});
			ne.innerHTML = buff;
		}
    };
		
	$.fn.removeRow = function(index){
		var nodeObj = $(this).get(0);
		var total = nodeObj.rows.length;
		//console.log('current len:'+ total +" deleting "+ index);
		
		if(index !== NaN && index < total && index >= 0){
			nodeObj.deleteRow(index);
		}
    };
	
	$.fn.row = function(index){
		var nodeObj = $(this).get(0);
		var total = nodeObj.rows.length;
		var values = [];
		if(index !== NaN && index < total && index >= 0 ){
			var theRow = nodeObj.rows[index];
			for(var i = 0;i< theRow.cells.length;i++){
                values.push(theRow.cells[i].innerHTML);
            };
		} else if(index instanceof HTMLElement) {
			var theRow = index;
			for(var i = 0;i< theRow.cells.length;i++){
                values.push(theRow.cells[i].innerHTML);
            };
		}
		return values;
	};
	
	function Accordion(root, conf) {
		
		var self = this, 
			 tabs = root.find(conf.tabs);
			 
		
		// make sure tabs and panes are found
		if (!tabs.length)  { tabs = root.children(); }

		
		// public methods
		$.extend(this, {
			click: function(i, e) {
				
				if (typeof i == 'string' && i.replace("#", "")) {
					tab = tabs.filter("[href*=" + i.replace("#", "") + "]");
					i = Math.max(tabs.index(tab), 0);
				}
								
				var tab = $(tabs[i]); 			
				
				// possibility to cancel click action				
				e = e || $.Event();
				e.type = "onBeforeClick";

				if(tab.hasClass(conf.collapsed)){
					var sib = tab.parent('td').parent('tr').siblings('tr');
					$(sib).show();
					e.type = "onClick";
					
					tab.removeClass(conf.collapsed);	
					tab.addClass(conf.expanded);				
				}else if(tab.hasClass(conf.expanded)){
					$(tab.parent('td').parent('tr').siblings('tr')).hide();
					e.type = "onClick";
					
					tab.removeClass(conf.expanded);	
					tab.addClass(conf.collapsed);	
				}
				return self;
			}
	     
		
		});

		// callbacks	
		$.each("onBeforeClick,onClick".split(","), function(i, name) {
				
			// configuration
			if ($.isFunction(conf[name])) {
				$(self).bind(name, conf[name]); 
			}

			// API
			self[name] = function(fn) {
				if (fn) { $(self).bind(name, fn); }
				return self;	
			};
		});
		
		// setup click actions for each tab
		tabs.each(function(i) { 				
			$(this).bind(conf.event, function(e) {
				self.click(i, e);
				return e.preventDefault();
			});			
		});
		
	}
	
	// jQuery plugin implementation
	$.fn.accordion = function(conf) {
		
		if ($.isFunction(conf)) {
			conf = {onBeforeClick: conf};
		}
		
		// setup conf
		aconf = $.extend({}, {
			onBeforeClick: null,
			expanded:'expanded',
			collapsed:'collapsed',
			onClick: null, 
			event: 'click',
		}, conf);		
		
		
		this.each(function() {
			el = new Accordion($(this), aconf);
		});		
		
		return aconf.api ? el: this;		
	};	
	
})(jq);